package com.ruizhong.centercontroll.util;


import java.awt.AWTException;
import java.awt.HeadlessException;
import java.awt.Robot;
import java.awt.Toolkit;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.StringSelection;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Executors;
import java.util.concurrent.LinkedBlockingDeque;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

public class ControllerUtil {
    private static List<DataInputStream> disList = new ArrayList<>();

    private static ThreadPoolExecutor executor;

    public static Robot robot;

    public static void init() throws AWTException {
        executor = new ThreadPoolExecutor(5, 5, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingDeque<>(), Executors.defaultThreadFactory(), new ThreadPoolExecutor.AbortPolicy());
        robot = new Robot();
    }

    public static void cleanClients() throws IOException {
        for (DataInputStream dataInputStream : disList) {
            dataInputStream.close();
        }
    }

    public static synchronized void addNewClient(final Socket socket) {
        try {
            final ObjectInputStream ois = new ObjectInputStream(socket.getInputStream());
            executor.execute(new Runnable() {
                public void run() {
                    while (true) {
                        try {
                            Object o = ois.readObject();
                            if (o == null)
                                continue;
                            if (o instanceof KeyInfo)
                                ControllerUtil.keyEvent((KeyInfo)o);
                        } catch (IOException e) {
                            e.printStackTrace();
                            try {
                                socket.close();
                                break;
                            } catch (IOException ex) {
                                ex.printStackTrace();
                            }
                        } catch (ClassNotFoundException e) {
                            e.printStackTrace();
                        }
                    }
                }
            });
        } catch (IOException e) {
            e.printStackTrace();
            try {
                socket.close();
            } catch (IOException ex) {
                ex.printStackTrace();
            }
            return;
        }
    }

    public static void keyEvent(KeyInfo info) {
        if (!info.getSystem().equals("ipad")) {
            int type = info.getEvent();
            if (type == 401) {
                robot.keyPress(info.getKey_code());
            } else if (type == 402) {
                robot.keyRelease(info.getKey_code());
            }
        } else {
            String word;
            int x;
            String[] wordSplit;
            int y;
            String type = info.getType();
            int id = info.getId();
            switch (type) {
                case "word":
                    if (id == 1) {
                        try {
                            Clipboard systemClipboard = Toolkit.getDefaultToolkit().getSystemClipboard();
                            StringSelection stringSelection = new StringSelection(info.getWord());
                            systemClipboard.setContents(stringSelection, null);
                            robot.keyPress(17);
                            robot.keyPress(86);
                            robot.keyRelease(86);
                            robot.keyRelease(17);
                        } catch (HeadlessException e) {
                            e.printStackTrace();
                        }
                        break;
                    }
                    word = info.getWord();
                    word.replace("[", "");
                    word.replace("]", "");
                    wordSplit = word.split(",");
                    inputHotKey(wordSplit);
                    break;
                case "mouse":
                    Recalculate(info);
                    x = (int)(info.getX() / info.getFitWidth() * Server.remoteImageWidth);
                    y = (int)(info.getY() / info.getFitHeight() * Server.remoteImageHeight);
                    if (id == 503) {
                        for (int i = 0; i < 10; i++)
                            robot.mouseMove(x, y);
                        System.out.println("x="+ x + ",y=" + y);
                        break;
                    }
                    if (id == 501) {
                        for (int i = 0; i < 10; i++)
                            robot.mouseMove(x, y);
                        robot.mousePress(16);
                        break;
                    }
                    if (id == 502) {
                        robot.mouseRelease(16);
                        System.out.println("x="+ x + ",y=" + y);
                        break;
                    }
                    if (id == 1007) {
                        robot.mousePress(4096);
                        robot.mouseRelease(4096);
                    }
                    break;
            }
        }
    }

    private static void inputHotKey(String[] wordSplit) {
        int i;
        for (i = 0; i < wordSplit.length; i++) {
            if (wordSplit[i].contains("Ctrl"))
                robot.keyPress(17);
            if (wordSplit[i].contains("Shift"))
                robot.keyPress(16);
            if (wordSplit[i].contains("F1"))
                robot.keyPress(112);
            if (wordSplit[i].contains("F2"))
                robot.keyPress(113);
            if (wordSplit[i].contains("F3"))
                robot.keyPress(114);
            if (wordSplit[i].contains("F4"))
                robot.keyPress(115);
            if (wordSplit[i].contains("F5"))
                robot.keyPress(116);
        }
        for (i = 0; i < wordSplit.length; i++) {
            if (wordSplit[i].contains("Ctrl"))
                robot.keyRelease(17);
            if (wordSplit[i].contains("Shift"))
                robot.keyRelease(16);
            if (wordSplit[i].contains("F1"))
                robot.keyRelease(112);
            if (wordSplit[i].contains("F2"))
                robot.keyRelease(113);
            if (wordSplit[i].contains("F3"))
                robot.keyRelease(114);
            if (wordSplit[i].contains("F4"))
                robot.keyRelease(115);
            if (wordSplit[i].contains("F5"))
                robot.keyRelease(116);
        }
    }

    private static void Recalculate(KeyInfo info) {
        double textureHeight = info.getFitHeight();
        double textureWidth = info.getFitWidth();
       getRealFitWidthAndRealFitHeight(info);
//       计算realX和RealY
        double realX,realY;
        realX = info.getX() - ((textureWidth - info.getFitWidth()) / 2);
        realY = info.getY()-((textureHeight-info.getFitHeight())/2);
       if (realX<0 || realY <0){
           return;
       }
        info.setX(realX);
        info.setY(realY);

    }

    private static void getRealFitWidthAndRealFitHeight(KeyInfo info) {
        double textureHeight = info.getFitHeight();
        double textureWidth = info.getFitWidth();
        double R = Server.remoteImageWidth / Server.remoteImageHeight;
        double realFitWidth,realFitHeight=0.0;
        realFitHeight = textureHeight;
        realFitWidth = realFitHeight*R;
        if (realFitWidth> textureWidth){
            realFitWidth = textureWidth;
            realFitHeight = realFitWidth/R;
        }
        info.setFitHeight(realFitHeight);
        info.setFitWidth(realFitWidth);
    }

}
